<?php
// +----------------------------------------------------------------------
// | Copyright (c) 2023 yoncron All rights reserved.
// +----------------------------------------------------------------------
// | Author: yoncron <yoncron@163.com>
// +----------------------------------------------------------------------
namespace app\controller\app\im;

use app\controller\app\AppBase;
use app\model\GroupMembersModel;
use app\model\MessageModel;
use app\model\UserModel;
use app\service\LoginRecord;
use app\service\Route;
use GatewayWorker\Lib\Gateway;
use support\Request;
use support\Response;
use Ramsey\Uuid\Uuid;

Gateway::$registerAddress = config('app.gateway_register_address');

class Chat extends AppBase
{
    public function beforeAction(){
        $rtn = parent::beforeAction();
        if($rtn instanceof Response){
            return $rtn;
        }
    }

    public static function send_welcome_tip($user_id=0,$app_id=0){
        $userObj = new UserModel([],$app_id);
        $fromUser = $userObj->find(10000);
        $message_data = [
            'key' => Uuid::uuid4()->toString(),
            'name' => $fromUser['username'],
            'realname' => $fromUser['realname'],
            'avatar' => $fromUser['avatar'],
            'id' => $fromUser['user_id'],
            'type' => 'friend',
            'content' => htmlspecialchars('欢迎回到XXX。如果您在使用过程中有任何的问题或建议，可以随时告诉我们。'),
            'timestamp' => time() * 1000,
            'from_id' => $fromUser['user_id'],
            'from_name' => $fromUser['username'],
            'from_avatar' => $fromUser['avatar']
        ];
        $chat_message = array(
            'message_type' => 'chatMessage',
            'data' => $message_data
        );
        Gateway::sendToUid($user_id, json_encode($chat_message));
    }

    /**
     * description:绑定client_id
     * @Route(reqUrl="/im.chat.bind")
     * author:yoncron<yoncron@163.com>
     * data:2023/10/30
     */
    public function bind(Request $request){
        $userObj = new UserModel();
        $messageObj = new MessageModel();
        $client_id = input('client_id');
        //$platform = input('platform');
        $client_ip = $request->getRealIp($safe_mode=true);

        $_user = $userObj->where(['user_id' => $this->user_id])->find();
        LoginRecord::add('online',$_user['user_id'],'success',$client_ip);


        //多个设备登录，将另外一个踢下线
        if($_user['online_status']=='online'){
            Gateway::sendToUid($this->user_id,json_encode(['message_type' => 'quit']));
        }

        Gateway::bindUid($client_id, $this->user_id);


        $group_id_array = GroupMembersModel::where(['uid' => $this->user_id])->column('gid');
        if ($group_id_array) {
            foreach ($group_id_array as $gid) {
                Gateway::joinGroup($client_id, $gid);
            }
        }



        $userObj->where(['user_id' => $this->user_id])->update(['online_status'=>'online']);



        $unread_notice_count = 0;
        // 这个用户没有退出时间
        if ($_user) {
            $logout_timestamp = $_user['logout_time'];
            $groups = $group_id_array ? "'" . implode("','", $group_id_array) . "'" : -1;
            // 用户有退出时间，则查询message数据库，找出这个用户的所有时间大于$logout_timestamp的消息，这些消息是离线消息
            $unread_message = $messageObj->where("(`to` = ".$this->user_id." OR `to` in ($groups)) AND timestamp> $logout_timestamp")->limit(500)->column('data');
            // 读取完毕后更新logout_timestamp，避免多页面时重复提示离线消息
            $userObj->where(['user_id' => $this->user_id])->update(['logout_time'=>time(),'last_login_ip'=>$client_ip]);
        }
        if (empty($unread_message)) {
            $unread_message = array();
        }

        // 通知所有客户端当前用户上线
        //$online_message = array('message_type' => 'online', 'id' => $this->user_id);
        //Gateway::sendToAll(json_encode($online_message));
        
        $rtn_data = [
            'unread_message'=>$unread_message,
            'unread_message_count'=>count($unread_message)
        ];
        return success($rtn_data,0,'登录成功');
    }

    /**
     * description:发送消息
     * @Route(reqUrl="/im.chat.send.msg")
     * author:yoncron<yoncron@163.com>
     * data:2023/10/30
     */
    public function send_msg(){
        $messageModel = new MessageModel();

        $data = input("data");
        $data = $data ?? json_decode(input("json_data"),true);
        $from = $this->user_id;
        $to = $data['to']['id'];
        $type = $data['type'];

        $message_data = [
            'key' => $data['key'],
            'name' => $type === 'friend' ? $data['mine']['name'] : $data['to']['name'],
            'avatar' => $type === 'friend' ? $data['mine']['avatar'] : $data['to']['avatar'],
            'id' => $type === 'friend' ? $from : $to,
            'type' => $type,
            'content' => htmlspecialchars($data['content']),
            'timestamp' => time() * 1000,
            'from_id' => $from,
            'from_name' => $data['mine']['name'],
            'from_avatar' => $data['mine']['avatar']
        ];


        $chat_message = array(
            'message_type' => 'chatMessage',
            'data' => $message_data
        );

        switch ($type) {
            // 私聊
            case 'friend':
                Gateway::sendToUid($to, json_encode($chat_message));
                break;
            // 群聊
            case 'group':
                Gateway::sendToGroup($to, json_encode($chat_message), Gateway::getClientIdByUid($this->user_id));
                break;
        }

        // 记录消息到message表
        $res = $messageModel->insert(array(
            'from' => $from,
            'to' => $to,
            'data' => json_encode($message_data),
            'timestamp' => time(),
            'type' => $type
        ));
        return $res ? success(null,0,"发送成功") : error(1,"发送失败");
    }

    /**
     * description:接收到消息后的回调
     * @Route(reqUrl="/im.chat.msg.accept.callback")
     * author:yoncron<yoncron@163.com>
     * data:2023/10/30
     */
    public function msg_accept_callback(){
        $userModel = new UserModel();
        $userModel->where(['user_id' => $this->user_id])->update(['logout_time'=>time()]);
        return success();
    }

    /**
     * description:已读标记
     * @Route(reqUrl="/im.chat.msg.read")
     * author:yoncron<yoncron@163.com>
     * data:2023/10/30
     */
    public function msg_read(){

    }

    /**
     * description:正在输入
     * @Route(reqUrl="/im.chat.be.inputting")
     * author:yoncron<yoncron@163.com>
     * data:2023/10/30
     */
    public function be_inputting(){

    }


}